﻿''' <summary>
'''  Abzu Core Commands registrars and handlers
''' </summary>
''' <remarks></remarks>
Module commandHandlers
    Public Event incSyn(ByRef ex As Abzu.incorrectSyntax)
    ''' <summary>
    ''' Initialize basic commands
    ''' </summary>
    ''' <remarks></remarks>
    Sub PopulateCommands()
        'TODO: finish me
        AddHandler incSyn, AddressOf _incorrectSyntax_eventhandler

        command.registerCommand("help", String.Format("Provides help information for {0} registered commands", My.Application.Info.AssemblyName))
        command.cmdList("help").args.Add("[command]", "Optional, command to display help of, can specify more then 1")
        AddHandler command.cmdList("help").exec, AddressOf commandHandlers.help_EventHandler


        command.registerCommand("version", String.Format("Displays version of {0} ", My.Application.Info.AssemblyName))
        AddHandler command.cmdList("version").exec, AddressOf commandHandlers.version_EventHandler

        'AddHandler command.cmdList("").exec, AddressOf PopulateCommands

        'command.registerCommand("configure", String.Format("Manage {0} related settings", My.Application.Info.AssemblyName))
        'command.cmdList("configure").args.Add("settingName", "Name of the setting to be changed")
        'command.cmdList("configure").args.Add("newSetting", "New value to set to")


        'cmdSyntaxList.Add("addServer [instanceName] [game] [gameManager]")
        command.registerCommand("addServer", "register a new server instance with RSMA")
        command.cmdList("addServer").args.Add("instanceName", "Name of the Server instance to be added")
        command.cmdList("addServer").args.Add("game", "Game Type of the new Server Instance")
        command.cmdList("addServer").args.Add("gameManager", "gameManager of the new Server Instance")

        'cmdSyntaxList.Add("editServer [instanceName] [game] [gameManager]")
        command.registerCommand("editServer", "edit existing server instance")
        command.cmdList("editServer").args.Add("instanceName", " New Name of the Server instance")
        command.cmdList("editServer").args.Add("game", "New Game Type of the Server Instance")
        command.cmdList("editServer").args.Add("gameManager", "New gameManager of the Server Instance")



        'cmdSyntaxList.Add("generateFile [fileType] [serverInstance] [opt: targetLocation]")
        command.registerCommand("generateFile", "edit existing server instance")
        command.cmdList("generateFile").args.Add("fileType", " New Name of the Server instance")
        command.cmdList("generateFile").args.Add("serverInstance", "New Game Type of the Server Instance")
        command.cmdList("generateFile").args.Add("opt: targetLocation", "[optional] target location of the file to be generated")


        'cmdSyntaxList.Add("configure [module] [param]")
        command.registerCommand("configure", "manipulate module parameters")
        command.cmdList("configure").params.Add("/m", "negate module")
        command.cmdList("configure").params.Add("/lm", "List modules")
        command.cmdList("configure").args.Add("module", "module name space to edit")
        command.cmdList("configure").args.Add("param", "param to modify")
        command.cmdList("configure").args.Add("newValue", "new value to set to")
        AddHandler command.cmdList("configure").exec, AddressOf commandHandlers.configure_EventHandler
        'command.cmdList("configure").args.Add("opt: targetLocation", "[optional] target location of the file to be generated")


        command.registerCommand("print", "print a module property or object")
        command.cmdList("print").params.Add("/m", "negate module")
        command.cmdList("print").params.Add("/lm", "List modules")
        command.cmdList("print").args.Add("module", "module name space to edit")
        command.cmdList("print").args.Add("param", "param to print")
        AddHandler command.cmdList("print").exec, AddressOf commandHandlers.print_EventHandler

        'cmdSyntaxList.Add("configure vault [ipAddress] [url]")
        command.registerCommand("addGameManager", "register game manager")
        command.cmdList("addGameManager").args.Add("name", "name of the game manager")
        command.cmdList("addGameManager").args.Add("regex", "param to modify")

        command.registerCommand("addGame", "register game manager")
        command.cmdList("addGame").args.Add("name", "name of the game manager")
        command.cmdList("addGame").args.Add("gameManager", "game manager")

        command.registerCommand("loadComplex", "load complex file templates")
        'cmdSyntaxList.Add("configure FileMonitoring [mode]")

        'cmdSyntaxList.Add("status") TODO: 

        'cmdSyntaxList.Add("addGame [game name] [game Manager]")
        'cmdSyntaxList.Add("registerFile [Server Instance] [file Type] [Location] [Watch mode]")
        'cmdSyntaxList.Add("addReservist([name])")
        'cmdSyntaxList.Add("removeReservist([name])")
        'cmdSyntaxList.Add("activateSlot [Reservist name] [guid] [Server Instance]")
        'cmdSyntaxList.Add("deactivateSlot [Reservist name] [guid] [Server Instance]")
        'cmdSyntaxList.Add("addAdmin [name] [guid] [rank] [server Instance]")
        'cmdSyntaxList.Add("removeAdmin [name] [guid] [rank] [server Instance]")
        'cmdSyntaxList.Add("List –d [what] [param1]")
        'cmdSyntaxList.Add("serverInstanceName [what: reservists, admins]")
    End Sub
    Public Sub main()

        Dim tempkvp As New KeyValuePair(Of String, String)("", "")
        Dim a_kvp() As KeyValuePair(Of String, String) = {tempkvp, tempkvp}
        ' new string(,) {{"a", "b"}, {"c", "d"}, {"e", "f"}}
    End Sub
    Public Function convert_arrayTo_kvp(ByRef array(,) As Object, ByRef _dict As SortedDictionary(Of Object, Object))
        Dim maxDim0 As Integer = UBound(array, 1)
        For i As Integer = 0 To maxDim0
            _dict.Add(array(i, 0), array(i, 1))
        Next i
    End Function
#Region "Command Event Handlers"
    Public Function help_EventHandler(Optional ByRef params() As String = Nothing, Optional ByRef args() As String = Nothing)
        Dim i_desc As Integer = Console.BufferWidth - 21
        If (params Is Nothing) Then
            'If (params Is Nothing Or (params.Length = 1 And params(0) = "")) Then
            If (args Is Nothing) Then 'no params, no args
                'display all basic commands
                For Each cmd As KeyValuePair(Of String, command) In command.cmdList
                    If (cmd.Value.description.Length > i_desc) Then 'need to split this into two lines with a trailing carrage return
                        'lets be efficent and just tack it to a var
                        Dim i_desc_lineSpan As Integer = ((cmd.Value.description.Length / i_desc) - 1)
                        Console.WriteLine("{0,-20}{1}", cmd.Key, cmd.Value.description.Substring(0, i_desc))
                        Dim i_pointer As Integer = i_desc

                        While i_pointer < cmd.Value.description.Length 'while our pointer is not beyond the length of the command description
                            Console.WriteLine("{0,-20}{1}", " ", cmd.Value.description.Substring(i_pointer, (cmd.Value.description.Length - i_pointer)))
                            i_pointer += i_desc
                        End While
                        Console.WriteLine()
                    Else : Console.WriteLine("{0,-20}{1}", cmd.Key, cmd.Value.description)
                    End If

                Next cmd
            Else 'no params but args
                If (args.Count = 1) Then 'print the help for the passed command
                    Try
                        Console.WriteLine(command.cmdList(args(0)).help())
                        'Catch ex As Exception
                    Catch ex As KeyNotFoundException
                        _error.printerror("Command not found", False, False)
                    End Try
                ElseIf (args.Count > 1) Then 'print help for all of the pass args/commands
                    Try
                        Console.WriteLine()
                        For Each cmd As String In args
                            Console.WriteLine(command.cmdList(cmd).help())
                            Console.WriteLine()
                        Next
                        'Catch ex As Exception
                    Catch ex As KeyNotFoundException
                        _error.printerror("Command not found", False, False)
                    End Try
                End If

            End If
        Else
            If (args Is Nothing) Then ' params, no args
            Else 'params and args                   

            End If
        End If
    End Function
    Public Function version_EventHandler(Optional ByRef params() As String = Nothing, Optional ByRef args() As String = Nothing)
        If (params Is Nothing) Then
            If (args Is Nothing) Then 'no params, no args
                Console.WriteLine(My.Application.Info.Version)
            Else 'no params but args
            End If
        Else
            If (args Is Nothing) Then ' params, no args
            Else 'params and args                   

            End If
        End If
    End Function
    Public Function configure_EventHandler(Optional ByRef params() As String = Nothing, Optional ByRef args() As String = Nothing)
        If (params Is Nothing) Then
            If (args Is Nothing) Then 'no params, no args
                'My.Settings.Properties.
                'My.Settings.Setting.add
            Else 'no params but args
                If (args.Length = 1) Then 'set setting to null
                ElseIf (args.Length < 1) Then
                    _error.printerror("Not enough parameters passed", False, False)
                Else
                    Try
                        My.Settings.Item(args(0)) = args(1)
                        My.Settings.Save()
                    Catch ex As System.Configuration.SettingsPropertyNotFoundException
                        _error.printerror(ex.Message, True, False)
                    End Try
                End If
            End If
        Else
            If (args Is Nothing) Then ' params, no args
            Else 'params and args                   

            End If
        End If
    End Function
    Public Function print_EventHandler(Optional ByRef params() As String = Nothing, Optional ByRef args() As String = Nothing)
        If (params Is Nothing) Then
            If (args Is Nothing) Then 'no params, no args
                Throw New incorrectSyntax("print")

            Else 'no params but args
                If (args.Length = 1) Then 'set setting to null
                    Try
                        Console.WriteLine(vbTab & "Setting " & """" & args(0) & """" & " = " & """" & My.Settings.Item(args(0)) & """")
                    Catch ex As System.Configuration.SettingsPropertyNotFoundException
                        _error.printerror(ex.Message, True, False)
                    End Try
                ElseIf (args.Length < 1) Then
                    _error.printerror("Not enough parameters passed", False, False)
                Else
                    Try
                        Console.WriteLine(String.Format("Setting '{0}' = '{1}'", args(0), My.Settings.Item(args(0))))
                    Catch ex As System.Configuration.SettingsPropertyNotFoundException
                        _error.printerror(ex.Message, True, False)
                    End Try
                End If
            End If
        Else
            If (args Is Nothing) Then ' params, no args
            Else 'params and args                   

            End If
        End If
    End Function
#End Region
    Public Function blank_EventHandler(Optional ByRef params() As String = Nothing, Optional ByRef args() As String = Nothing)
        If (params Is Nothing) Then
            If (args Is Nothing) Then 'no params, no args
                Console.WriteLine(My.Application.Info.Version)
            Else 'no params but args
            End If
        Else
            If (args Is Nothing) Then ' params, no args
            Else 'params and args                   

            End If
        End If
    End Function

    Public Function examineProcess(ByVal id As Integer)
        Try
            Dim proc As System.Diagnostics.Process = System.Diagnostics.Process.GetProcessById(id)
            'is process unresponsive?
            If (proc.Responding) Then
                'Dim _errorReader As New System.IO.TextReader
                'proc.BeginErrorReadLine()

                'proc.StandardError.Synchronized(_errorReader)
                'proc.HasExited
                'proc.Kill()
                'proc.StandardOutput
                'proc.EnableRaisingEvents
                'proc.InitializeLifetimeService()
                'proc.WaitForInputIdle()
                'ut o.. should we restart or wait
                'TODO user configurable set time for wait for unreponsive process until its forcefully restarted
            End If
        Catch ex As Exception

        End Try

    End Function
    Private Function _incorrectSyntax_eventhandler(Optional ByRef ex As Abzu.incorrectSyntax = Nothing)
        If (ex Is Nothing) Then
            _error.printerror("Invalid Syntax", False, False)
        Else

            _error.printerror("Invalid Syntax", False, False)
            If (command.cmdList.ContainsKey(ex.cmd)) Then
                Console.WriteLine(command.cmdList(ex.cmd).help)
            Else
                Console.WriteLine("how the hell did we get here!")
            End If

        End If

    End Function
End Module
Class incorrectSyntax
    Inherits System.Exception
    Private _cmdValue As String
    Public Property cmd As String
        Get
            Return _cmdValue
        End Get
        Set(ByVal value As String)
            _cmdValue = value
        End Set
    End Property
    Public Sub New(ByVal _cmd As String)
        MyBase.New("Incorrect command Syntax entered for " & """" & _cmd & """")
    End Sub
End Class

